#pragma once

#include <mcp/config.h>
#include <mcp/transport/transport.h>

#include <memory>
#include <string>
#include <vector>
#include <functional>
#include <atomic>
#include <thread>
#include <mutex>
#include <condition_variable>

namespace mcp {
namespace transport {

/// @brief Standard I/O transport for stdin/stdout communication
class StdioTransport : public Transport {
public:
    StdioTransport();
    explicit StdioTransport(bool use_stderr = false);
    ~StdioTransport() override;

    // Transport interface implementation
    bool start() override;
    void stop() override;
    bool is_connected() const override;
    bool send(const json::Value& message) override;
    std::coroutine_handle<> send_async(const json::Value& message) override;
    void set_message_handler(MessageHandler handler) override;
    void set_error_handler(ErrorHandler handler) override;
    void set_close_handler(CloseHandler handler) override;
    void set_open_handler(OpenHandler handler) override;
    std::string get_type() const override;
    json::Value get_capabilities() const override;

    /// @brief Set buffer size for reading
    /// @param size Buffer size in bytes
    void set_buffer_size(size_t size);

    /// @brief Get number of bytes read
    /// @return Bytes read counter
    size_t get_bytes_read() const;

    /// @brief Get number of bytes written
    /// @return Bytes written counter
    size_t get_bytes_written() const;

private:
    struct Impl;
    std::unique_ptr<Impl> impl_;
};

/// @brief Stdio transport factory
class StdioTransportFactory : public TransportFactory {
public:
    StdioTransportFactory() = default;

    // TransportFactory interface implementation
    std::unique_ptr<Transport> create() override;
    std::string get_type() const override;
    std::vector<std::string> get_supported_schemes() const override;
};

} // namespace transport
} // namespace mcp